/**
 * Alipay.com Inc.
 * Copyright (c) 2004-2013 All Rights Reserved.
 */
package com.pingan.mobilegw.core.service.invoke.proxy;

import com.pingan.mobilegw.adapterservice.*;
import com.pingan.mobilegw.core.model.ServiceConfig;
import com.pingan.mobilegw.core.model.comm.TargetRequestObject;
import com.pingan.mobilegw.core.model.constant.ContextConstant;
import com.pingan.mobilegw.core.model.exception.MgwException;
import com.pingan.mobilegw.core.service.invoke.async.Async;
import com.pingan.mobilegw.core.service.invoke.async.AsyncListenerImpl;
import com.pingan.mobilegw.core.service.util.ContextUtil;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.stereotype.Service;

import javax.servlet.AsyncContext;
import javax.servlet.AsyncListener;
import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.UndeclaredThrowableException;
import java.util.List;

/**
 * Mofa的Spi调用代理
 * 
 * @author jiadao
 * @version $Id: MobileAdapterServiceInvokeProxyImpl.java, v 0.1 2013-4-8 下午9:22:58 jiadao Exp $
 */
@Component
public class MobileAdapterWithCallbackProxyImpl implements MofaInvokeProxy {

    /** logger */
    private static final Log logger        = LogFactory
                                                  .getLog(MobileAdapterWithCallbackProxyImpl.class);


    private AsyncListener       asyncListener = new AsyncListenerImpl();

    @Autowired
    private MobileAdapterService mobileAdapterService;

    public TargetResponseObject invoke(TargetRequestObject targetObject) {
        ServiceConfig serviceConfig = targetObject.getServiceConfig();
        HttpServletRequest request = targetObject.getGatewayRequest().getHttpRequest();


        try {

            // 异步调用前的处理，保存上下文，设置超时等信息
            Async.context.put(targetObject.getUniqueId(), targetObject.getGatewayRequest());
            AsyncContext asyncContext = request.startAsync();
            asyncContext.setTimeout(1000);
            asyncContext.addListener(asyncListener);
            request.setAttribute(ContextConstant.REQUEST_ID, targetObject.getUniqueId());

            // 远程调用
            return mobileAdapterService.mobileService(targetObject.getUniqueId(), targetObject
                .getMobileContext(), targetObject.getRequestData());

        } catch (UndeclaredThrowableException e) {
           /** LoggerUtil.error(logger, e, "远程调用服务异常，operationType=",
                serviceConfig.getOperationType(), ",SysName=", serviceConfig.getSysName(),
                ",InterfaceName=", serviceConfig.getInterfaceType(), ",MethodName=", serviceConfig
                    .getMethodName());
*/
            // 删除上下文信息，避免内存泄漏
            Async.context.remove(targetObject.getUniqueId());
            ContextUtil.setTag(request, ContextConstant.AYSNC_ERROR);

            // 调用超时
           //TODO if (e.getUndeclaredThrowable() instanceof HSFTimeOutException) {
                //throw new MgwException(ResultEnum.RequestTimeOut, e);
            //}
            // 其他调用异常
            throw new MgwException(ResultEnum.RemoteAccessException, e);
        }

    }


}
